﻿//处理socket消息
package com.victim.snake.user
{
	
	import flash.events.ProgressEvent;
	import flash.events.Event;
	import flash.errors.IOError;
	import flash.sampler.Sample;
	import flash.display.Sprite;
	import flash.utils.ByteArray;
	import flash.text.TextField;
	import flash.text.TextFieldType;
	import fl.controls.progressBarClasses.IndeterminateBar;
	import fl.controls.Button;	
	import fl.controls.List;		
	import fl.controls.DataGrid;
	import fl.controls.TextArea;	
	
	import com.victim.snake.graphics.LandSprite;
	import com.victim.snake.graphics.MainSprite;	
	import com.victim.snake.graphics.PlaySprite;	
	import com.victim.snake.graphics.playClass.GameOverSprite;	
	import com.victim.snake.graphics.RoomSprite;
	import com.victim.snake.graphics.mainClass.RoomListSprite;
	import com.victim.snake.graphics.ChatSprite;
	import com.victim.snake.snake.Body;	
	import com.victim.snake.snake.Snake;	
	import com.victim.snake.player.Player;
	import com.victim.snake.room.RoomBo;
	import com.victim.snake.room.Room;
	import com.victim.snake.snake.SnakeStyle;
	import com.victim.snake.snake.SnakeStyleEvent;
	import com.victim.snake.player.PlayerBo;
	import com.victim.snake.map.Map;
	import com.victim.snake.map.MapEvent;
	import com.victim.snake.snake.Food;
	



	public class ProcessMsg
	{
		static public var errorText:TextField=new TextField();

		//处理接收到的消息
		static public function processMsg(msg:Msg):void
		{			
			//trace(msg.type);
			switch (msg.type)
			{
				case 1 :	//接收确认连接消息，发送即将登录请求
					var ba:ByteArray=new ByteArray();
					ba.writeByte(2);			//消息类型;
					ba.writeShort(0);			//消息内容的长度;
					ProcessMsg.socketSend(ba);
					ba.clear();
					break;
				case 2 :	//接收可登陆确认，显示登陆界面
					var landSprite:LandSprite = new LandSprite();
					User.setLandSprite(landSprite);					
					User.getStage().addChildAt(landSprite,0);
					User.getStage().focus=landSprite.acount;	//设置焦点
					break;
				case 3 :	//判断登录，显示主界面					
					var loginStr:String=msg.getUTF8Content();
					var loginArr:Array=loginStr.split(";");
					
					//如果登陆成功
					if (loginArr[0] == "1")					
					{						
						//trace("登陆成功");
						User.getPlayer().setUid(int(loginArr[1]));
						var mainSprite:MainSprite=new MainSprite();
						User.setMainSprite(mainSprite);
						User.getStage().removeChildAt(0);			//删除登录界面;
						User.getStage().addChildAt(mainSprite,0);	//显示主界面
						Map.getAllMap();	//向服务器发送加载所有地图请求
						new Food(0,0,0,0,0,0).loadBtm();	//下载食物图片
						
					}else if(loginArr[0] == "2"){						
						ProcessMsg.errorText.text="密码错误，请确认密码是否正确";
						ProcessMsg.errorText.x=100;
						ProcessMsg.errorText.y=100;
						
						//显示错误信息
						User.getLandSprite().addChildAt(ProcessMsg.errorText,3);
						
						//将用户名和密码输入框设置为可用
						TextField(User.getLandSprite().getChildAt(0)).mouseEnabled=true;	
						TextField(User.getLandSprite().getChildAt(1)).mouseEnabled=true;
					}
					break;
				case 4 :	//接收房间列表数据
					//trace("接收房间数据");
					var roomListStr:String=msg.getUTF8Content();
					//trace(roomListStr);
					User.getMainSprite().addRoomItem(new Room(roomListStr));
					User.getMainSprite().setPage();
					//trace(roomListStr);
					
					/*//////原dataGrid列表
					//添加到房间显示列表（roomListSprite）
					var roomList:DataGrid=DataGrid(User.getMainSprite().getChildAt(0));
					roomList.addItem({roomId:roomArray[0],roomTitle:roomArray[1],players:roomArray[2],master:roomArray[3]});
					roomList.sortItemsOn("players",Array.NUMERIC);	//对列表进行排序
					
					//如果列表不为空,默认选择第行，并将加入按钮设为可用
					if(roomList.length>0){
						roomList.selectedIndex=0;
						User.getMainSprite().JoinBtnMouseEnabled(true);
					}else{
						User.getMainSprite().JoinBtnMouseEnabled(false);
					}
					////原dataGrid列表*/
					
					
					
					//roomList.addItem(roomArray[0],roomArray[1],roomArray[2],roomArray[3],roomArray[0]);					
					//添加到User的房间列表
					//var roomListArray:Array=User.getRoomList();
//					var playerForRoomList:Player=new Player();
//					playerForRoomList.setUid(roomArray[4]);
//					playerForRoomList.setUserName(roomArray[3]);
//					roomListArray.push(new Room(roomArray[1],roomArray[0],playerForRoomList));
					//var roomList:List=List(User.getMainSprite().getChildAt(0));
					//roomList.addItem({label:roomArray[0]+" "+roomArray[1]+" "+ roomArray[3]+" "+roomArray[2],date:roomArray[0]});
					break;
					
				case 5:	//服务器返回当前无房间消息
					var roomLists:DataGrid=DataGrid(User.getMainSprite().getChildAt(0));
					//roomLists.addItem({label:"无房间",date:-1});
					break;
				case 6:	//进入房间
					var roomStr:String=msg.getUTF8Content();	//取得房间消息
					//var roomArray1:Array = roomStr.split(";");	//分析房间消息
					User.setRoom(new Room(roomStr));	//创建房间
					var roomSprite:RoomSprite = User.getRoomSprite();	//取得房间界面
					roomSprite.reSet();	//重新设置房间界面类的数据
					User.getStage().removeChildAt(0);
					User.getStage().addChildAt(roomSprite,User.getStage().numChildren);	//显示房间界面
					//trace(roomStr);
					break;
				case 7:	//某玩家准备消息				
					//trace("接收到玩家准备消息")
					var playerReadyStr:String=msg.getUTF8Content();	//取得某ID玩家准备或非准备消息
					var playerReadyArray:Array = playerReadyStr.split(";");	//分析房间消息
					RoomBo.setPlayerReadyOrUnReadyById(playerReadyArray[0],RoomBo.tranReadyOrUnReadyStrMsg(playerReadyArray[1]));
					break;
				case 8:	//确定开始游戏
					//trace(1);
					User.getPlaySprite().start();
					break;
				case 9:	//其它用户加入房间消息					
					var playerStr:String=msg.getUTF8Content();	//取得房间消息
					var playerStrArray:Array=playerStr.split(";");
					var player:Player=new Player();
					player.setUserName(playerStrArray[1]);
					player.setUid(int(playerStrArray[2]));
					player.setSnakeStyle(playerStrArray[3]);
					//是否自动准备
					if(playerStrArray[4]=="1"){
						player.setIsReady(true);
					}else{
						player.setIsReady(false);
					}
					RoomBo.addPlayer(player,int(playerStrArray[5]),int(playerStrArray[0]));
					//User.getRoom().addPlayer(player,int(playerStrArray[0]));	//将新用户添加到房间的用户列表
					//User.getRoomSprite().addPlayer(int(playerStrArray[0]),player.getUserName());	//在房间显示界面添加新用户
					
					break;
				case 10:	//其它用户退出房间消息
					var userId:int = int(msg.getUTF8Content());	//取得退出用户id
					var player1:Player=new Player();
					player1.setUid(userId);
					var seat1:int=User.getRoom().reMovePlayer(player1);	//将用户移除（按玩家ID）
					//User.getRoomSprite().reMovePlayer(seat1);
					break;
				case 11:	//退出房间用户接收到服务器确认
					User.getPlayer().setIsReady(false);
					User.getStage().removeChild(User.getRoomSprite());
					User.getMainSprite().init();
					User.getRoomSprite().init();
					User.getStage().addChildAt(User.getMainSprite(),User.getStage().numChildren);
					User.setRoom(null);
					break;
				case 12:
					User.getErrorSprite().setErrorString("房间以满");
					User.getErrorSprite().visible=true;	//显示房间以满消息					
					break;
				case 13:
					User.getErrorSprite().setErrorString("房间以关闭或游戏以开始，请重新选择房间");
					User.getErrorSprite().visible=true;	//显示房间以满消息					
					break;
				case 14:	//设置房主消息
					var userId1:int = int(msg.getUTF8Content());	//取得房主id
					var player2:Player=new Player();
					player2.setUid(userId1);
					var seat2:int=User.getRoom().setMaster(player2);	//将用户设为房主
					
					//User.getRoomSprite().refreshState();	//更新房间状态（按钮是否显示或可用等）
					
					
					break;
				case 15:	//房主点击开始游戏后，接收服务器发来的蛇信息,并创建蛇
					var snakeInfo:String=msg.getUTF8Content();
					var snakeInfoArr:Array=snakeInfo.split(";");
					User.getRoom().init();	//初使化房间
					
					//创建房间里的每条蛇
					var si:int=0;
					while(si<snakeInfoArr.length-1){
						var snake:Snake=new Snake(snakeInfoArr[si],snakeInfoArr[si+1],snakeInfoArr[si+4],snakeInfoArr[si+2],snakeInfoArr[si+3],20,20,Body.colors[snakeInfoArr[si+6]],snakeInfoArr[si+5],int(snakeInfoArr[si+7]),snakeInfoArr[si+8]);
						User.getRoom().setSnake(snake);
						if(snake.getId()<0){	//如果是电脑
							User.getRoom().setComputer(snake);	//添加到电脑蛇列表
							User.getRoom().setComputerCount(User.getRoom().getComputerCount()+1);
						}else if(int(snakeInfoArr[si])!=User.getPlayer().getUid()){
							User.getRoom().setUsers(snake);	//添加到玩家蛇列表
						}else if(int(snakeInfoArr[si])==User.getPlayer().getUid()){							
							snake.setUserCurrent(true);	//自己的蛇
							User.setSnake(snake);	//自己的蛇
						}
						si+=9;						
					}
					
					var playSprite:PlaySprite=new PlaySprite()	//创建游戏界面
					User.setPlaySprite(playSprite);	
					User.getStage().removeChildAt(0);
					User.getStage().addChild(playSprite);	//将游戏界面添加到舞台
					
					
					break;
				case 16:	//服务器返回的蛇改变方向信息
					var direStr:String=msg.getUTF8Content();					
					var direArr:Array=direStr.split(";");
					var direSnake:Snake=User.getRoom().getSnake(int(direArr[0]));	//取得要改变方向的蛇
					direSnake.setCoordinates(direArr.slice(1,direArr.length-1));	//计算拉扯值并重置蛇(坐标及方向)
					direSnake.setDirection(direArr[direArr.length-1]);	//改变蛇转向
					//direSnake.moveByCoordinate();	//向前移动一格
					
					break;
				case 17:	//处理服务器发来的延时分析消息  (以过时)
					var delayByte:ByteArray=new ByteArray();
					delayByte.writeByte(11);	//消息类型
					delayByte.writeShort(2);	//消息内容的长度
					delayByte.writeByte(msg[0]);	
					delayByte.writeByte(msg[1]);	
					ProcessMsg.socketSend(delayByte);
					break;
				case 18:	//服务器返回的蛇死亡消息
					var deathStr:String=msg.getUTF8Content();
					var deathArr:Array=deathStr.split(";");
					
					User.getRoom().getSnake(int(deathArr[0])).setDeath(deathArr[deathArr.length-1]==0?false:true);	//设置蛇死亡
					User.getRoom().getSnake(int(deathArr[0])).setCoordinates(deathArr.slice(1,deathArr.length-1));	//设置蛇的位置
					
					//如果为当前蛇
					/*if(User.getSnake().getId()==int(deathArr[0])){
						User.getPlaySprite().snakeDeath();	//显示当前蛇死亡的效果(画面变暗，显示死亡对话框)
					}*/
					//trace(deathArr[deathArr.length-1]==0?false:true);
					break;
				case 19:	//接收服务器返回的食物消息
					//trace("接收服务器返回的食物消息");
					var foodStr:String=msg.getUTF8Content();
					var foodArr:Array=foodStr.split(";");
					User.getPlaySprite().addFood(foodArr[0],foodArr[1],foodArr[2],foodArr[3],foodArr[4],foodArr[5]);
					break;
				case 20:	//蛇吃到食物消息
				//trace("蛇吃到食物消息");
					var growStr:String=msg.getUTF8Content();
					var growArr:Array=growStr.split(";");
					//按食物状态是增长还是加速等
					switch (int(growArr[1])){
						case 1 :	
							User.getRoom().getSnake(int(growArr[0])).grow(1);
							break;
						case 2 :	
							User.getRoom().getSnake(int(growArr[0])).acceleration(1);
							break;
						default:
							User.getRoom().getSnake(int(growArr[0])).grow(1);
							;
					}	
					
					//trace(User.getRoom().getSnake(int(growArr[0])).getBodys().length);
					break;
				case 21:	//删除食物消息
					//trace("服务器返回吃到食物ID："+msg[0])
					User.getPlaySprite().removeFood(msg[0]);
					break;
				case 22:	//结束游戏					
					User.getPlaySprite().stop();	//停止游戏
					var goSprite:GameOverSprite=new GameOverSprite(msg);	//创建游戏结束对话框
					//User.getRoom().init();	//初使化房间
					User.getStage().addChild(goSprite);	//显示游戏结束对话框
					
					break;
				case 23:	//接收聊天消息
					var talkArray:Array=msg.getUTF8Content().split(";");
					User.getChatSprite().addTalkMsg(talkArray[0],talkArray[1]);
					break;
				case 24:	//接收蛇样式属性
					var snakeStylePropertyArray:Array=msg.getUTF8Content().split(";");
					var snakeStyle:SnakeStyle=SnakeStyle.getStyle(snakeStylePropertyArray[1]);
					snakeStyle.setSnakeStyleProperty(int(snakeStylePropertyArray[0]),snakeStylePropertyArray[1],int(snakeStylePropertyArray[2]),
													 int(snakeStylePropertyArray[3]),int(snakeStylePropertyArray[4]),int(snakeStylePropertyArray[5]),
													 int(snakeStylePropertyArray[6]),int(snakeStylePropertyArray[7]),int(snakeStylePropertyArray[8]),
													 int(snakeStylePropertyArray[9]),int(snakeStylePropertyArray[10]),int(snakeStylePropertyArray[11]),
													 int(snakeStylePropertyArray[12]),snakeStylePropertyArray[13]);
					//一但接收到服务器发来的蛇样式消息，则显示到房间界面的蛇样式显示框中
					snakeStyle.addEventListener(SnakeStyleEvent.IsLoaded,User.getRoomSprite().showSnakeStyleEvent);
					snakeStyle.loading();
					break;
				case 25:	//玩家选择蛇样式
					var changeSnakeStyleArray:Array=msg.getUTF8Content().split(";");
					RoomBo.setSnakeStyleById(changeSnakeStyleArray[0],changeSnakeStyleArray[1]);
					break;
				case 26:	//服务器发来的自动准备确认消息	0,不自动准备	1,自动准备
					var autoReadyStr:String=msg.getUTF8Content();
					if(autoReadyStr=="1"){
						PlayerBo.setAutoReady(User.getPlayer(),true);
					}else{
						PlayerBo.setAutoReady(User.getPlayer(),false);
					}
					break;
				case 27:	//服务器发来的地图消息				
					var mapStrArray:Array=msg.getUTF8Content().split(";");
					//trace(msg.getUTF8Content());
					var map:Map=Map.getMap(mapStrArray[1]);
					map.setCName(mapStrArray[2]);					
					User.getMainSprite().createRoomSprite.addMapItem(map);	//将地图信息添加到创建房间窗口地图选择列表
					//如果有房间界面
					if(User.hasRoomSprite()){
						User.getRoomSprite().addMapItem(map);	//将地图信息添加到房间界面地图选择列表
					}
					map.load();
					break;
				case 28:	//服务器发来的设置地图消息
					var changeMapStr:String=msg.getUTF8Content();
					//trace(msg.getUTF8Content());
					User.getRoom().setMap(changeMapStr);
					break;
				case 29:	//服务器发来的设置游戏模式消息					
					User.getRoom().setGameMode(int(msg.getUTF8Content()));
					break;
				case 30:	//服务器发来的设置游戏模式计数器消息					
					User.getRoom().setModeCounter(int(msg.getUTF8Content()));
					break;
				case 31:	//服务器发来的设置某玩家队伍消息 (用户ID+用户队伍)
					var setPlayerGroupArray:Array=msg.getUTF8Content().split(";");
					User.getRoom().setPlayerGroup(int(setPlayerGroupArray[0]),int(setPlayerGroupArray[1]));
					break;
				case 32:	//服务器发来的复活房间内某只蛇消息
					trace("服务器发来复活蛇消息");
					var rebirthSnakeStrArry:Array=msg.getUTF8Content().split(";");					
					
					User.getRoom().deleteSnake(int(rebirthSnakeStrArry[0]));	//从房间里删除死亡的蛇
					
					//创建一条新蛇
					var rebirthSnake:com.victim.snake.snake.Snake=new Snake(rebirthSnakeStrArry[0],rebirthSnakeStrArry[1],rebirthSnakeStrArry[4],rebirthSnakeStrArry[2],rebirthSnakeStrArry[3],20,20,Body.colors[rebirthSnakeStrArry[6]],rebirthSnakeStrArry[5],int(rebirthSnakeStrArry[7]),rebirthSnakeStrArry[8]);
					//如果是当前玩家的蛇
					if(int(rebirthSnakeStrArry[0])==User.getPlayer().getUid()){
						//将新蛇设为当前蛇
						rebirthSnake.setUserCurrent(true);	
						User.setSnake(rebirthSnake);	
						User.getPlaySprite().setSnake();
					}else{	//如果不是当前蛇
						User.getRoom().setUsers(rebirthSnake);	//将蛇放入其它玩家蛇集合中	
					}
					User.getRoom().setSnake(rebirthSnake);	//将新蛇放入所有玩家蛇集合中
					
					//rebirthSnake.setDeath(false);
					break;
				default:
					trace("有问题");
					
			}

		}
		
		

		//当收到服务器发出消息后
		static public function socketRead(event:ProgressEvent):void
		{			
			var readFlag:int = 0;	//读取标识
			var contentLength:int = 0;	//消息内容长度
			var msg:Msg=new Msg();
			var msgLength:ByteArray=new ByteArray();
			
			//trace(1);
			
			//如果输入缓冲区中有数据
			while (User.getSocket().bytesAvailable!=0)
			{				
				//读取消息类型
				if(readFlag==0){
					msg.type=User.getSocket().readByte();
					//trace("消息类型："+msg.type);
				}				
				
				//读取消息长度
				if (readFlag == 1)
				{					
					msgLength[0]=User.getSocket().readByte();
					//trace("缓冲区剩余长度："+User.getSocket().bytesAvailable);
				}
				
				if(readFlag ==2){
					msgLength[1]=User.getSocket().readByte();
					contentLength = msgLength.readShort();
					//trace("消息长度："+contentLength);
					//trace("缓冲区剩余长度："+User.getSocket().bytesAvailable);
				}
				
				//读取消息
				if(readFlag>2 ){					
					msg.writeByte(User.getSocket().readByte());
					//trace("缓冲区剩余长度："+User.getSocket().bytesAvailable);
				}

				//当读取到消息内容长度的数据时,则认为读取到一条完整的消息
				if (readFlag == (contentLength+2))
				{
					
					//if(User.getSocket().bytesAvailable!=0){
//						trace(readFlag+"   "+contentLength+"   "+User.getSocket().bytesAvailable);						
//					}
					
					//trace(msg.toString());
					
					ProcessMsg.processMsg(msg);	//处理消息;
					
					msgLength.clear();
					msg.clear();
					contentLength=0;
					readFlag=0;
					
					continue;
					return;
				}				
				
				
				
				readFlag +=  1;
			}
			//this.addEventListener(Event.ENTER_FRAME,this.show);//添加帧频事件
		}


		//向服务器发送消息
		static public function socketSend(msg:ByteArray):void
		{
			
			//调试代码
/*			msg.position=0;
			var s:String="";
			while(msg.bytesAvailable!=0){
				s+=msg.readByte()+" ";
			}
			msg.position=1;
			//trace("发送消息长度："+msg.readShort());
			trace(s);
			trace("");			
			msg.position=0;*/
			//调试结束
			
			
			try{
				User.getSocket().writeBytes(msg,0,msg.length);
			}catch(e:IOError){
				User.getErrorSprite().setErrorString("连接超时，请刷新页面重新登陆");
				User.getErrorSprite().visible=true;//显示房间以满消息
			}
			User.getSocket().flush();
		}


		//当连接上服务器后调用方法(向服务器发送byte值1,用于与服务器端确认连接);
		static public function begin(event:Event):void
		{
			var ba:ByteArray=new ByteArray();
			ba.writeByte(1);			//消息类型;
			ba.writeShort(0);			//消息内容的长度;
			ProcessMsg.socketSend(ba);
			ba.clear();
		}

		
		
		//生成utf8消息
		static public function generateUTF8Msg(msgType:int,strMsg):ByteArray{
			var msg:ByteArray=new ByteArray();
			var strMsgByte:ByteArray=new ByteArray();
			strMsgByte.writeMultiByte(strMsg,"UTF-8");
			msg.writeByte(msgType);
			//trace("发送消息内容长度:"+strMsgByte.length);
			msg.writeShort(strMsgByte.length);
			msg.writeBytes(strMsgByte,0,strMsgByte.length);
			return msg;
		}
	}
}